/* SGATOR
 * plugin.h
 */

#ifndef SGPLUGIN_H
#define SGPLUGIN_H

#include "base/types.h"
#include "types.h"
#include "sgladspa.h"

#define SG_PLUGIN_ELEM 1
#define SG_PLUGIN_MOD 2
#define SG_PLUGIN_SG 3
#define SG_PLUGIN_LADSPA 4

/* var mode */
#define SG_VAR_TYPE_FLOAT 1
#define SG_VAR_TYPE_INT 2
#define SG_VAR_TYPE_BOOL 4
#define SG_VAR_TYPE_MASK 7

#define sg_var_type_is_float(t) (t & SG_VAR_TYPE_FLOAT)
#define sg_var_type_is_int(t) (t & SG_VAR_TYPE_INT)
#define sg_var_type_is_bool(t) (t & SG_VAR_TYPE_BOOL)

#define SG_PORT_TYPE_INPUT 0
#define SG_PORT_TYPE_OUTPUT 1
#define SG_PORT_TYPE_AUDIO 0
#define SG_PORT_TYPE_CONTROL 2

#define sg_port_is_input(t) (!(t & SG_PORT_TYPE_OUTPUT))
#define sg_port_is_output(t) (t & SG_PORT_TYPE_OUTPUT)
#define sg_port_is_audio(t) (!(t & SG_PORT_TYPE_CONTROL))
#define sg_port_is_control(t) (t & SG_PORT_TYPE_CONTROL)

struct _SgPortDesc {
  char *name;
  SgInt type;
  SgFloat value;
  SgFloat upper_limit;
  SgFloat lower_limit;
};

struct _SgVarDesc {
  char *name;
  SgInt type;
  SgVal value;
  SgVal upper_limit;
  SgVal lower_limit;
};

#define SGV(v,u,l) (SgVal)v,(SgVal)u,(SgVal)l

typedef void (*SgRunFun)(SgElem*, SgULong s, SgULong ns);
typedef void (*SgConnectFun)(SgElem*, SgULong port);
typedef void (*SgChangeFun)(SgElem*, SgUShort varnb);
typedef void (*SgMakeFun)(SgElem*);
typedef void (*SgInitFun)(SgElem*);
typedef void (*SgResetFun)(SgElem*);
typedef void (*SgRemoveFun)(SgElem*);

struct _SgElemPluginDesc {
  char *id;
  SgUInt ports_nb;
  SgUShort vars_nb;
  SgPortDesc *ports;
  SgVarDesc *vars;
  SgBool needownbuffs;
  SgRunFun on_run;
  SgConnectFun on_connect;
  SgChangeFun on_change;
  SgMakeFun on_make;
  SgInitFun on_init;
  SgResetFun on_reset;
  SgRemoveFun on_remove;
  char *name;
  char *author;
  char *copyright;
  char *help;
};

struct _SgModPluginDesc {
  char *id;
  SgUInt ports_nb;
  SgUShort vars_nb;
  SgPortDesc *ports;
  SgVarDesc *vars;
  SgBool needownbuffs;
  SgRunFun on_run;
  SgConnectFun on_connect;
  SgChangeFun on_change;
  SgMakeFun on_make;
  SgInitFun on_init;
  SgResetFun on_reset;
  SgRemoveFun on_remove;
  char *name;
  char *author;
  char *copyright;
  char *help;
};

union _SgPluginDescP {
  SgElemPluginDesc *sgelem;
  SgModPluginDesc *sgmod;
  SgLadspaPluginDesc *ladspa;
  void *oth;
};

typedef SgPluginDescP (*SgPluginDescFun)(SgULong idx);

/* type for the structure describing a collection of plugins in a
   shared object file (corresponding to the symbol sg_plugins_info) */
typedef struct {
  SgUInt type;
  char *id;
  SgPluginDescFun sg_plugin_desc_fun;
  char *name;
  char *author;
  char *copyright;
  char *help;
} SgPluginsInfo;

void sg_plugin_register(SgPluginDescP, SgInt type);
SgBool sg_plugin_check(SgPluginDescP, SgInt type);

#endif

/* end */

